/**
 * @fileOverview orbit controller
 * @author huangtonger@aliyun.com
 */

const Base = require('../../../simpleBase');
const Global = require('../global');
const Satellite = require('./satellite/');
const { vec2, isString } = require('../util/');

class Controller extends Base {
  getDefaultCfg() {
    return {
      satellite: [],
      satelliteCache: []
    };
  }
  init() {
    const satelliteCfg = this.satellite;
    const diagram = this.diagram;
    const defaultCfg = {
      diagram
    };
    const graph = diagram.getGraph();
    graph.addBehaviour('orbit');
    satelliteCfg.forEach(subCfg => {
      if (isString(subCfg)) {
        this.satelliteCache.push(new Satellite[subCfg](defaultCfg));
      } else {
        this.satelliteCache.push(new Satellite({
          ...defaultCfg,
          ...subCfg
        }));
      }
    });
  }
  /**
   * @param {object} item - item
   * @param {object} point - diagram
   */
  layout(item, point) {
    const diagram = this.diagram;
    const graph = diagram.getGraph();
    const { satelliteCache } = this;
    const box = item.getBBox();
    const { centerX, centerY } = box;
    const zoom = diagram.getZoom();
    const gap = Global.orbitGap / zoom;
    const satellites = satelliteCache.filter(satellite => {
      return satellite.isVisible();
    });
    const vp = [ point.x - centerX, point.y - centerY ];
    const vpl = vec2.length(vp);
    const exl = box.width / 2 + gap;
    const vt = vec2.scale([], vp, exl / vpl);
    satellites.forEach(satellite => {
      const dom = satellite.getDOM();
      const halfDomWidth = dom.width() / 2;
      const domPoint = graph.getDomPoint({
        x: vt[0] + centerX,
        y: vt[1] + centerY
      });
      dom.css({
        top: domPoint.y - halfDomWidth + 'px',
        left: domPoint.x - halfDomWidth + 'px'
      });
    });
  }
  show(item) {
    const { satelliteCache } = this;
    satelliteCache.forEach(satellite => {
      if (satellite.enable()) {
        satellite.item = item;
        satellite.show();
      }
    });
  }
  hide() {
    const { satelliteCache } = this;
    satelliteCache.forEach(satellite => {
      satellite.hide();
    });
  }
}

module.exports = Controller;
